package com.cleaningcloud.cld.service.impl;

import com.cleaningcloud.cld.api.domain.CldStaff;
import com.cleaningcloud.cld.domain.CldProject;
import com.cleaningcloud.cld.domain.CldProjectGroups;
import com.cleaningcloud.cld.domain.CldProjectPost;
import com.cleaningcloud.cld.domain.dto.CldMaterialAllocateDto;
import com.cleaningcloud.cld.domain.dto.CldProjectPostDto;
import com.cleaningcloud.cld.domain.dto.CldRestbreaksCalendarMemberDto;
import com.cleaningcloud.cld.domain.vo.*;
import com.cleaningcloud.cld.mapper.*;
import com.cleaningcloud.cld.mapper.other.WarehouseInventoryMapper;
import com.cleaningcloud.cld.service.ICldMaterialAllocateService;
import com.cleaningcloud.cld.service.PublicCommonService;
import com.cleaningcloud.common.core.utils.DateUtils;
import com.cleaningcloud.common.security.utils.DictUtils;
import io.seata.spring.annotation.GlobalTransactional;
import org.jetbrains.annotations.NotNull;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;


@Service
public class PublicCommonServiceImpl implements PublicCommonService {


    @Autowired
    private CldProjectMapper projectMapper;

    @Autowired
    private CldProjectGroupsMapper projectGroupsMapper;

    @Autowired
    private CldProjectPostMapper projectPostMapper;

    @Autowired
    private CldStaffMapper staffMapper;

    @Autowired
    private CldStaffContractMapper staffContractMapper;

    @Autowired
    private WarehouseInventoryMapper warehouseInventoryMapper;

    @Autowired
    private ICldMaterialAllocateService cldMaterialAllocateService;

    @Autowired
    private CldAssetsRecordMapper cldAssetsRecordMapper;

    @Autowired
    private CldTrainIecturerMapper trainIecturerMapper;

    @Autowired
    private CldProjectPostMapper cldProjectPostMapper;

    @Autowired
    private CldRestbreaksCalendarMemberMapper cldRestbreaksCalendarMemberMapper;

    private static CldMaterialAllocateDto getCldMaterialAllocateDto(WarehouseInventoryVo warehouseInventoryVo, CldStaff cldStaff) {
        CldMaterialAllocateDto cldMaterialAllocateDto = new CldMaterialAllocateDto();
        cldMaterialAllocateDto.setMaterialOutId(warehouseInventoryVo.getWareId());
        cldMaterialAllocateDto.setMaterialInId(warehouseInventoryVo.getWarePid());
        cldMaterialAllocateDto.setAllocateType(2L);
        cldMaterialAllocateDto.setIsConfirm(1L);
        cldMaterialAllocateDto.setRemark("[" + cldStaff.getStaffName() + "]项目解绑,物资调回项目仓");
        cldMaterialAllocateDto.setDetailsList(warehouseInventoryVo.getDetailsList());
        return cldMaterialAllocateDto;
    }

    @Override
    public List<ProjectSelect> selectedProjectJob(int level) {
        List<ProjectSelect> result = new ArrayList<>();
        // 查询项目区域
        Map<String, String> projectRegionMap = DictUtils.getDictDataMap("cld_project_region");
        // 查询项目组字典
        Map<String, String> projectGroupMap = DictUtils.getDictDataMap("cld_project_groups");
        // 查询项目岗位字典
        Map<String, String> projectPostMap = DictUtils.getDictDataMap("cld_project_post");
        for (String key : projectRegionMap.keySet()) {
            ProjectSelect regoinMap = new ProjectSelect();
            // 根据项目区域查询项目
            regoinMap.setLabel(projectRegionMap.get(key));
            regoinMap.setValue(Long.valueOf(key));
            CldProject projectQuery = new CldProject();
            projectQuery.getParams().put("contractStatus", 1);
            projectQuery.setProjectRegion(Long.valueOf(key));
            List<CldProjectContractVo> projectList = projectMapper.selectCldProjectContractList(projectQuery);
            regoinMap.setDisabled(projectList.isEmpty());
            if (level >= 1) {
                List<ProjectSelect> projectListMap = new ArrayList<>();
                for (CldProjectContractVo cldProjectVo : projectList) {
                    ProjectSelect projectMap = new ProjectSelect();
                    projectMap.setValue(Long.valueOf(cldProjectVo.getProjectId().toString()));
                    projectMap.setLabel(cldProjectVo.getProjectName());
                    // 根据项目查询项目组表
                    CldProjectGroups groupsQuery = new CldProjectGroups();
                    groupsQuery.setProjectId(cldProjectVo.getProjectId());
                    List<CldProjectGroups> groupsList = projectGroupsMapper.selectCldProjectGroupsList(groupsQuery);
                    projectMap.setDisabled(groupsList.isEmpty());
                    if (level >= 2) {
                        List<ProjectSelect> groupsListMap = new ArrayList<>();
                        for (CldProjectGroups groups : groupsList) {
                            ProjectSelect groupMap = new ProjectSelect();
                            groupMap.setValue(Long.valueOf(groups.getGroupName()));
                            groupMap.setLabel(projectGroupMap.get(groups.getGroupName()));
                            // 根据项目小组查询小组下岗位列表
                            CldProjectPostDto postQuery = new CldProjectPostDto();
                            postQuery.setProjectId(cldProjectVo.getProjectId());
                            postQuery.setProjectGroupsId(groups.getProjectGroupsId());
                            postQuery.setFlag(0L);
                            List<CldProjectPostSetVo> postList = projectPostMapper.selectCldProjectPostList(postQuery);
                            groupMap.setDisabled(postList.isEmpty());
                            if (level >= 3) {
                                List<ProjectSelect> postListMap = new ArrayList<>();
                                for (CldProjectPost cldProjectPost : postList) {
                                    if (cldProjectPost.getProjectPostName() != null) {
                                        ProjectSelect postMap = new ProjectSelect();
                                        // 职务 岗位 班次 都不允许为空
                                        if (cldProjectPost.getProjectPostName() == null ||
                                                cldProjectPost.getProjectDuitsName() == null ||
                                                cldProjectPost.getClassesId() == null || cldProjectPost.getStaffId() != null) {
                                            postMap.setDisabled(true);
                                        }
                                        postMap.setLabel(projectPostMap.get(cldProjectPost.getProjectPostName().toString()));
                                        postMap.setValue(Long.valueOf(cldProjectPost.getProjectPostId().toString()));
                                        postListMap.add(postMap);
                                    }
                                }
                                groupMap.setChildren(postListMap);
                            }
                            groupsListMap.add(groupMap);
                        }
                        projectMap.setChildren(groupsListMap);
                    }
                    projectListMap.add(projectMap);
                }
                // 设置项目
                regoinMap.setChildren(projectListMap);
            }
            // 设置项目区域
            result.add(regoinMap);
        }
        return result;
    }

    @Override
    public List<ProjectSelect> selectedProjectGroupStaff() {
        List<ProjectSelect> result = new ArrayList<>();
        // 查询项目组字典
        Map<String, String> projectGroupMap = DictUtils.getDictDataMap("cld_project_groups");
        CldProject projectQuery = new CldProject();
        projectQuery.getParams().put("contractStatus", 1);
        List<CldProjectContractVo> projectList = projectMapper.selectCldProjectContractList(projectQuery);
        for (CldProjectContractVo cldProjectVo : projectList) {
            ProjectSelect projectMap = new ProjectSelect();
            projectMap.setValue(Long.valueOf(cldProjectVo.getProjectId().toString()));
            projectMap.setLabel(cldProjectVo.getProjectName());
            // 根据项目查询项目组表
            CldProjectGroups groupsQuery = new CldProjectGroups();
            groupsQuery.setProjectId(cldProjectVo.getProjectId());
            List<CldProjectGroups> groupsList = projectGroupsMapper.selectCldProjectGroupsList(groupsQuery);
            List<ProjectSelect> groupsListMap = new ArrayList<>();
            for (CldProjectGroups groups : groupsList) {
                ProjectSelect groupMap = new ProjectSelect();
                groupMap.setValue(Long.valueOf(groups.getGroupName()));
                groupMap.setLabel(projectGroupMap.get(groups.getGroupName()));
                // 根据项目小组及项目id查询在岗员工
                CldProjectPostDto query = new CldProjectPostDto();
                query.setProjectId(cldProjectVo.getProjectId());
                query.setProjectGroupsId(groups.getProjectGroupsId());
                query.setIsMasterDuits(1L);
                getProjectPostStaff(groupsListMap, groupMap, query, null, projectGroupMap.get(groups.getGroupName()), Long.valueOf(groups.getGroupName()));
            }
            projectMap.setChildren(groupsListMap);
            result.add(projectMap);
        }
        return result;
    }

    private void getProjectPostStaff(List<ProjectSelect> groupsListMap, ProjectSelect groupMap, CldProjectPostDto query, Map<String, String> projectPostMap, String groupName, Long groupId) {
        List<CldProjectPostSetVo> postStaffList = projectPostMapper.selectCldProjectPostList(query);
        List<ProjectSelect> staffList = new ArrayList<>();
        for (CldProjectPostSetVo cldProjectPost : postStaffList) {
            if (cldProjectPost.getStaffId() != null) {
                ProjectSelect staffMap = new ProjectSelect();
                staffMap.setLabel(cldProjectPost.getStaffName());
                staffMap.setStaffName(cldProjectPost.getStaffName());
                staffMap.setStaffId(cldProjectPost.getStaffId());
                if (projectPostMap != null && cldProjectPost.getProjectPostName() != null) {
                    staffMap.setPostName(projectPostMap.get(cldProjectPost.getProjectPostName().toString()));
                    staffMap.setPostId(cldProjectPost.getProjectPostName());
                }
                staffMap.setGroupName(groupName);
                staffMap.setGroupId(groupId);
                staffMap.setWareId(cldProjectPost.getWareId());
                staffMap.setValue(Long.valueOf(cldProjectPost.getStaffId().toString()));
                staffList.add(staffMap);
            }
        }
        groupMap.setChildren(staffList);
        groupsListMap.add(groupMap);
    }

    @Override
    public List<ProjectSelect> selectJobStaffByProjectId(Long projectId) {
        List<ProjectSelect> result = new ArrayList<>();
        // 查询项目组字典
        Map<String, String> projectGroupMap = DictUtils.getDictDataMap("cld_project_groups");
        // 查询项目岗位字典
        Map<String, String> projectPostMap = DictUtils.getDictDataMap("cld_project_post");
        // 查询项目岗位
        List<CldProjectPost> postList = projectPostMapper.selectProjectPostGroupByByProjectId(projectId);
        for (CldProjectPost projectPost : postList) {
            ProjectSelect postMap = new ProjectSelect();
            postMap.setLabel(projectPostMap.get(projectPost.getProjectPostName().toString()));
            postMap.setValue(Long.valueOf(projectPost.getProjectPostId().toString()));
            postMap.setPostId(projectPost.getProjectPostName());
            // 根据项目岗位及项目id查询在岗员工
            CldProjectPostDto query = new CldProjectPostDto();
            query.setProjectId(projectId);
            query.setProjectPostName(projectPost.getProjectPostName());
            query.setFlag(0L);
            query.setIsMasterDuits(1L);
            getProjectPostStaff(result, postMap, query, projectPostMap, null, null);
        }
        return result;
    }

    @Override
    public List<ProjectSelect> selectGroupStaffByProjectId(Long projectId, Long isMasterDuits) {
        List<ProjectSelect> result = new ArrayList<>();
        // 查询项目组字典
        Map<String, String> projectGroupMap = DictUtils.getDictDataMap("cld_project_groups");
        // 查询项目岗位字典
        Map<String, String> projectPostMap = DictUtils.getDictDataMap("cld_project_post");
        // 查询项目小组
        // 根据项目查询项目组表
        CldProjectGroups groupsQuery = new CldProjectGroups();
        groupsQuery.setProjectId(projectId);
        List<CldProjectGroups> groupsList = projectGroupsMapper.selectCldProjectGroupsList(groupsQuery);
        for (CldProjectGroups groups : groupsList) {
            ProjectSelect groupMap = new ProjectSelect();
            groupMap.setValue(Long.valueOf(groups.getGroupName()));
            groupMap.setLabel(projectGroupMap.get(groups.getGroupName()));
            // 根据项目小组及项目id查询在岗员工
            CldProjectPostDto query = new CldProjectPostDto();
            query.setProjectId(projectId);
            query.setIsMasterDuits(isMasterDuits);
            query.setProjectGroupsId(groups.getProjectGroupsId());
            getProjectPostStaff(result, groupMap, query, projectPostMap, projectGroupMap.get(groups.getGroupName()), Long.valueOf(groups.getGroupName()));
        }
        return result;
    }

    @Override
    @Transactional
    @GlobalTransactional(rollbackFor = Exception.class)
    public void staffOptions(Long staffId, Integer type, Long projectId, Long projectPostId) {
        // 查询员工信息
        CldStaff cldStaff = staffMapper.selectCldStaffByStaffId(staffId);
        List<CldProjectPostSetVo> postList = new ArrayList<>();
        if (cldStaff != null) {
            List<WarehouseInventoryVo> warehouseInventoryVoList = new ArrayList<>();
            // 员工状态为在岗时
            if (cldStaff.getStaffStatus() == 2) {
                // 解除项目岗位
                if (projectPostId == null) {
                    warehouseInventoryVoList = warehouseInventoryMapper.selectWarehouseInventoryListByStaffId(staffId);
                    projectPostMapper.unbindingPostByStaffId(staffId);
                    staffContractMapper.updateStaffContractStatusByStaffIdAndProjectId(3, staffId, projectId);
                    // 如该员工是某资产负责人 清空负责人字段
                    cldAssetsRecordMapper.updatePersonIdIsNullByStaffId(staffId);
                } else {
                    // 查询人员是否存在多个岗位
                    CldProjectPostDto query = new CldProjectPostDto();
                    query.setProjectPostId(projectPostId);
                    query.setProjectId(projectId);
                    query.setStaffId(staffId);
                    postList = cldProjectPostMapper.selectCldProjectPostList(query);
                    if (postList.isEmpty() || postList.size() == 1) {
                        staffContractMapper.updateStaffContractStatusByStaffIdAndProjectId(3, staffId, projectId);
                        // 如该员工是某资产负责人 清空负责人字段
                        cldAssetsRecordMapper.updatePersonIdIsNullByStaffId(staffId);
                    }
                    projectPostMapper.unbindingJobByPostId(projectPostId);
                    WarehouseInventoryVo warehouseInventoryVo = warehouseInventoryMapper.selectWarehouseInventoryListByPostId(projectPostId);
                    warehouseInventoryVoList.add(warehouseInventoryVo);
                }
                // 个人仓物资调回项目仓
                if (!warehouseInventoryVoList.isEmpty()) {
                    for (WarehouseInventoryVo warehouseInventoryVo : warehouseInventoryVoList) {
                        if(warehouseInventoryVo == null || warehouseInventoryVo.getDetailsList() == null || warehouseInventoryVo.getDetailsList().isEmpty()) {
                            continue;
                        }
                        // 物资调拨(个人仓物资调回项目仓
                        CldMaterialAllocateDto cldMaterialAllocateDto = getCldMaterialAllocateDto(warehouseInventoryVo, cldStaff);
                        cldMaterialAllocateDto.setIsConfirm(1L);
                        cldMaterialAllocateService.insertCldMaterialAllocate(cldMaterialAllocateDto);
                    }
                }
                // 清除人员排休记录
                CldRestbreaksCalendarMemberDto restbreaksCalendarMemberDto = new CldRestbreaksCalendarMemberDto();
                restbreaksCalendarMemberDto.setProjectId(projectId);
                restbreaksCalendarMemberDto.setProjectStaffId(staffId);
                restbreaksCalendarMemberDto.getParams().put("beginTime", DateUtils.dateTime(new Date()));
                List<CldRestbreaksCalendarMemberVo> restbreaksCalendarMemberVos = cldRestbreaksCalendarMemberMapper.selectCldRestbreaksCalendarMemberList(restbreaksCalendarMemberDto);
                List<Long> ids = new ArrayList<>();
                if(!restbreaksCalendarMemberVos.isEmpty()){
                    for (CldRestbreaksCalendarMemberVo restbreaksCalendarMemberVo : restbreaksCalendarMemberVos) {
                        ids.add(restbreaksCalendarMemberVo.getRestbreaksCalendarMemberId());
                    }
                    cldRestbreaksCalendarMemberMapper.deleteCldRestbreaksCalendarMemberByRestbreaksCalendarMemberIds(ids.toArray(new Long[0]));
                }
            }
            // 离职
            if (type == 1) {
                // 取消培训讲师任职
                trainIecturerMapper.unbindingCldTrainIecturerByStaffId(staffId);
                cldStaff.setStaffStatus(3);
            }
            // 拉黑
            if (type == 2) {
                cldStaff.setStaffStatus(4);
            }
            // 解绑
            if (type == 3) {
                if (postList.isEmpty() || postList.size() == 1) {
                    cldStaff.setStaffStatus(1);
                }
            }
            // 删除员工
            if (type == 4) {
                cldStaff.setFlag(1L);
            }
            staffMapper.updateCldStaff(cldStaff);
        }
    }


}
